﻿using GameStoreMinimalApi.WebApi.Entities;

namespace GameStoreMinimalApi.WebApi.Repositories;

public class InMemoryGamesRepository : IGamesRepository
{
    private readonly List<Game> _games = new()
    {
        new Game
        {
            Id = 1,
            Name = "Street Fighter",
            Genre = "Fighting",
            Price = 19.99m,
            ReleaseDate = new DateTime(1991, 2, 1),
            ImageUri = "https://placehold.co/100"
        },
        new Game
        {
            Id = 2,
            Name = "Final Fantasy XIV",
            Genre = "Roleplaying",
            Price = 59.99m,
            ReleaseDate = new DateTime(2010, 9, 30),
            ImageUri = "https://placehold.co/100"
        },
        new Game
        {
            Id = 3,
            Name = "Fifa 23",
            Genre = "Sports",
            Price = 69.99m,
            ReleaseDate = new DateTime(2022, 9, 27),
            ImageUri = "https://placehold.co/100"
        }
    };

    public async Task<IEnumerable<Game>> GetAllAsync(int pageNumber, int pageSize, string? filter)
    {
        var skipCount = (pageNumber - 1) * pageSize;

        return await Task.FromResult(FilterGames(filter).Skip(skipCount).Take(pageSize));
    }

    public async Task<Game?> GetAsync(int id)
    {
        return await Task.FromResult(_games.FirstOrDefault(x => x.Id == id));
    }

    public async Task CreateAsync(Game game)
    {
        game.Id = _games.Max(x => x.Id) + 1;
        _games.Add(game);

        await Task.CompletedTask;
    }

    public async Task UpdateAsync(Game updatedGame)
    {
        var index = _games.FindIndex(game => game.Id == updatedGame.Id);
        _games[index] = updatedGame;

        await Task.CompletedTask;
    }

    public async Task DeleteAsync(int id)
    {
        var index = _games.FindIndex(game => game.Id == id);
        _games.RemoveAt(index);

        await Task.CompletedTask;
    }

    public async Task<int> CountAsync(string? filter)
    {
        return await Task.FromResult(FilterGames(filter).Count());
    }

    private IEnumerable<Game> FilterGames(string? filter)
    {
        if (string.IsNullOrWhiteSpace(filter))
        {
            return _games;
        }

        return _games.Where(game => game.Name.Contains(filter) || game.Genre.Contains(filter));
    }
}
